package controller

import (
	"encoding/json"
	"github.com/gin-gonic/gin"
	"go.uber.org/zap"
	"shorturl/configs"
	"shorturl/global"
	"shorturl/model"
	"shorturl/utils"
	"strings"
	"time"
)

type UserController struct {
	BaseController
}

// Change 编辑用户信息
func (app UserController) Change(c *gin.Context) {
	var param = make(map[string]string)
	err := json.NewDecoder(c.Request.Body).Decode(&param)

	passwordByte, err := utils.RsaDecrypt(param["password"])

	if err != nil {
		logger.Error("RsaDecrypt password", zap.Error(err))
		app.Error(c, "参数错误")
		return
	}

	// 提取密文 123|4b48f809-6d8d-49f2-8dae-2b5418404230|1743244519487 格式为 原文+请求唯一标识+请求时间戳
	password := strings.Split(string(passwordByte), "|")[0]

	// 双层加密
	md5password := utils.Md5(password)

	// app salt
	config, _ := configs.ReadConfig(utils.GetRootPath() + "/config.json")

	//md5加密password
	password = utils.Sha256(md5password + config.App.Secret)

	var user model.User

	// 查询用户信息
	db := global.Db.Where("id = ?", c.GetInt("admin_user_id")).First(&user)

	// 更新customer
	user.Password = password
	user.UpdateAt = model.LocalTime(utils.GetDateTime())

	err = db.Save(&user).Error

	if err != nil {
		logger.Error("更新失败", zap.Error(err))
		app.Error(c, "更新失败")
		return
	}
	app.Success(c, "更新成功")
}

// Login 登录
func (app UserController) Login(c *gin.Context) {
	var param = make(map[string]string)

	var err error
	err = json.NewDecoder(c.Request.Body).Decode(&param)
	if err != nil {
		logger.Error("参数解析错误", zap.Error(err))
		app.Error(c, "参数解析错误")
		return
	}

	var user model.User

	passwordByte, err := utils.RsaDecrypt(param["password"])

	if err != nil {
		logger.Error("RsaDecrypt password", zap.Error(err))
		app.Error(c, "参数错误")
		return
	}

	// 提取密文 123|4b48f809-6d8d-49f2-8dae-2b5418404230|1743244519487 格式为 原文+请求唯一标识+请求时间戳
	password := strings.Split(string(passwordByte), "|")[0]

	//fmt.Println(password)

	// 双层加密
	md5password := utils.Md5(password)

	// app salt
	config, _ := configs.ReadConfig(utils.GetRootPath() + "/config.json")

	//md5加密password
	password = utils.Sha256(md5password + config.App.Secret)

	err = global.Db.Where("username = ? and password = ?", param["username"], password).First(&user).Error

	// 判断用户是否存在
	if err != nil {
		logger.Error("用户名或密码错误", zap.Error(err))
		app.Error(c, "用户名或密码错误")
		return
	}

	//生成token
	var token = user.CreateToken(user.Id)

	user.Token = token

	//更新token
	global.Db.Model(&user).Update("token", token).Update("update_at", time.Now())

	//返回用户数据 以及 token 不返回密码
	user.Password = ""
	app.Success(c, user)
}

// Add 添加用户
func (app UserController) Add(c *gin.Context) {
	user := model.User{}

	err := c.ShouldBindJSON(&user)
	if err != nil {
		logger.Error("参数解析错误", zap.Error(err))
		app.Error(c, "参数错误")
		return
	}

	// 双层加密
	md5password := utils.Md5(user.Password)

	// app salt
	config, _ := configs.ReadConfig(utils.GetRootPath() + "/config.json")

	//md5加密password
	password := utils.Sha256(md5password + config.App.Secret)

	user.Password = password

	user.Salt = config.App.Secret

	user.CreateAt = model.LocalTime(utils.GetDateTime())

	err = global.Db.Create(&user).Error

	if err != nil {
		logger.Error("添加失败", zap.Error(err))
		app.Error(c, "添加失败")
	} else {
		app.Success(c, "添加成功")
	}
}

// Delete 删除用户
func (app UserController) Delete(c *gin.Context) {
	id := c.Query("id")

	ids := strings.Split(id, ",")

	var user model.User

	err := global.Db.Where("id in (?)", ids).Delete(&user).Error

	if err != nil {
		logger.Error("删除失败", zap.Error(err))
		app.Error(c, "删除失败")
	} else {
		app.Success(c, "删除成功")
	}
}

// Update 更新用户
func (app UserController) Update(c *gin.Context) {
	user := model.User{}

	var err error
	err = c.ShouldBindJSON(&user)
	if err != nil {
		logger.Error("参数解析错误", zap.Error(err))
		app.Error(c, "参数错误")
		return
	}

	// 更新时间
	user.UpdateAt = model.LocalTime(utils.GetDateTime())

	if user.Password == "" {
		err = global.Db.Omit("password").Where("id = ?", user.Id).Save(&user).Error
	} else {
		// 双层加密
		md5password := utils.Md5(user.Password)

		// app salt
		config, _ := configs.ReadConfig(utils.GetRootPath() + "/config.json")

		//md5加密password
		password := utils.Sha256(md5password + config.App.Secret)

		user.Password = password

		err = global.Db.Where("id = ?", user.Id).Save(&user).Error
	}

	if err != nil {
		logger.Error("更新失败", zap.Error(err))
		app.Error(c, "更新失败")
	} else {
		app.Success(c, "更新成功")
	}
}

// Index 获取用户
func (app UserController) Index(c *gin.Context) {
	pageNo := c.DefaultQuery("pageNo", "1")
	pageSize := c.DefaultQuery("pageSize", "10")
	id := c.Query("id")
	username := c.Query("username")
	phone := c.Query("phone")

	var user []model.User

	var total int64

	// 把params["page"]转换成int
	page := utils.StrToInt(pageNo)
	size := utils.StrToInt(pageSize)

	if page <= 0 {
		page = 1
	}
	if size <= 0 {
		size = 10
	}

	query := global.Db.Model(&user)

	if id != "" {
		query = query.Where("id = ?", id)
	}

	if username != "" {
		query = query.Where("username like ?", "%"+username+"%")
	}

	if phone != "" {
		query = query.Where("phone like ?", "%"+phone+"%")
	}

	query.Find(&user).Count(&total)
	query.Offset((page - 1) * size).Order("id desc").Limit(size).Find(&user)

	var result = make(map[string]interface{})

	result["total"] = total

	result["list"] = user

	app.Success(c, result)
}
